/*
 * Created on 2005-1-25
 *
 * TODO To change the template for this generated file go to
 * Window - Preferences - Java - Code Style - Code Templates
 */
package com.nauu.atombuilder.parts;

import java.beans.PropertyChangeEvent;
import java.beans.PropertyChangeListener;
import java.util.ArrayList;
import java.util.List;

import org.eclipse.draw2d.BendpointConnectionRouter;
import org.eclipse.draw2d.IFigure;
import org.eclipse.draw2d.Label;
import org.eclipse.draw2d.ManhattanConnectionRouter;
import org.eclipse.draw2d.MidpointLocator;
import org.eclipse.draw2d.PolygonDecoration;
import org.eclipse.draw2d.PolylineConnection;
import org.eclipse.draw2d.RelativeBendpoint;
import org.eclipse.gef.EditPart;
import org.eclipse.gef.EditPolicy;
import org.eclipse.gef.editparts.AbstractConnectionEditPart;
import org.eclipse.gef.editpolicies.ConnectionEndpointEditPolicy;
import org.eclipse.swt.graphics.Color;
import org.eclipse.swt.graphics.RGB;

import com.nauu.atombuilder.modle.Connection;
import com.nauu.atombuilder.modle.ConnectionBendpoint;
import com.nauu.atombuilder.modle.Node;
import com.nauu.atombuilder.policies.ConnectionBendpointEditPolicy;
import com.nauu.atombuilder.policies.ConnectionEditPolicy;

/**
 * @author nauu
 *
 */
public class ConnectionPart extends AbstractConnectionEditPart implements PropertyChangeListener{

	
	public void activate() {
        super.activate();
        ((Connection) getModel()).addPropertyChangeListener(this);
    }

    public void deactivate() {
        super.deactivate();
        ((Connection) getModel()).removePropertyChangeListener(this);
    }
    
    private Connection getCastedModel() {
		return (Connection) getModel();
	}
	
    @Override
	public void propertyChange(PropertyChangeEvent evt) {
    	 String prop = evt.getPropertyName();
 		if (Connection.CHANGE_COLOR.equals(prop)) {
 			String[] color = getCastedModel().getLineColor().split(",");
 			((PolylineConnection) getFigure()).setForegroundColor(new Color(null, 
 					new RGB(Integer.valueOf(color[0]), Integer.valueOf(color[1]),Integer.valueOf(color[2]))));
 		}
 		if (Connection.CHANGE_STYLE.equals(prop)) {
 			((PolylineConnection) getFigure()).setLineStyle(getCastedModel().getLineStyle());
 		}
 		if (Connection.CHANGE_ACT_TYPE.equals(prop)) {
 			int type = getCastedModel().getActType();
 			switch (type) {
			case 0:
				((PolylineConnection) getFigure()).setLineStyle(Connection.TRACK);
				break;
			case 1:
				((PolylineConnection) getFigure()).setLineStyle(Connection.CLIP);
				break;
			case 2:
				((PolylineConnection) getFigure()).setLineStyle(Connection.GRID);
				break;

			default:
				break;
			}
 		}
 		if (Connection.CHANGE_ACT_NAME.equals(prop)) {
 			PolylineConnection conn = (PolylineConnection) getFigure();
 			Label label = (Label)conn.getChildren().get(1);
 			label.setText((String)evt.getNewValue());
 		}
 		if(Connection.PROP_BENDPOINT.equals(prop)){
 			refreshBendpoints();
 		}
 		
 		refreshSourceConnections();
	}

	protected IFigure createFigure() {
        PolylineConnection conn = new PolylineConnection();
        conn.setTargetDecoration(new PolygonDecoration());
        conn.setConnectionRouter(new BendpointConnectionRouter());
        conn.setLineWidth(2);
        
        Connection connModel = getCastedModel();
    	Node node = connModel.getTarget();
    	String lineColor = "0,0,0";
    	if(!node.getMode()){
//    		lineStyle = Connection.POPUP;
    		lineColor = "25,70,150";
    	}
    	int lineStyle = 0;
    	switch (connModel.getActType()) {
		case 0:
			lineStyle = Connection.TRACK;
			break;
		case 1:
			lineStyle = Connection.CLIP;
			break;
		case 2:
			lineStyle = Connection.GRID;
			break;
		default:
			break;
		}
    	
    	connModel.setModeType(node.getMode()==true?0:1);
    	
        String tmp = lineColor;
        if(tmp != null){
        	String[] color = tmp.split(",");
        	conn.setForegroundColor(new Color(null, 
        			new RGB(Integer.valueOf(color[0]), Integer.valueOf(color[1]),Integer.valueOf(color[2]))));
        }
		
		conn.setLineStyle(lineStyle);
        // add a label
        final Label label = new Label(getCastedModel().getActName());
        label.setOpaque(true);
        conn.add(label, new MidpointLocator(conn, 0));
        return conn;
    }

    protected void createEditPolicies() {
        installEditPolicy(EditPolicy.COMPONENT_ROLE, new ConnectionEditPolicy());
        installEditPolicy(EditPolicy.CONNECTION_ENDPOINTS_ROLE, new ConnectionEndpointEditPolicy());
        installEditPolicy(EditPolicy.CONNECTION_BENDPOINTS_ROLE, new ConnectionBendpointEditPolicy());
    }

    protected void refreshVisuals() {
    	refreshBendpoints();
    }

    public void setSelected(int value) {
        super.setSelected(value);
        if (value != EditPart.SELECTED_NONE)
            ((PolylineConnection) getFigure()).setLineWidth(3);
        else
            ((PolylineConnection) getFigure()).setLineWidth(2);
    }
    
    /**
   	 * Updates the bendpoints, based on the model.
   	 */
   	protected void refreshBendpoints() {
   		if (getConnectionFigure().getConnectionRouter() instanceof ManhattanConnectionRouter)
   			return;
   		List modelConstraint = getConnection().getBendpoints();
   		List figureConstraint = new ArrayList();
   		for (int i = 0; i < modelConstraint.size(); i++) {
   			ConnectionBendpoint wbp = (ConnectionBendpoint) modelConstraint.get(i);
   			RelativeBendpoint rbp = new RelativeBendpoint(getConnectionFigure());
   			rbp.setRelativeDimensions(wbp.getFirstRelativeDimension(),
   					wbp.getSecondRelativeDimension());
   			rbp.setWeight((i + 1) / ((float) modelConstraint.size() + 1));
   			figureConstraint.add(rbp);
   		}
   		getConnectionFigure().setRoutingConstraint(figureConstraint);
   	}
   	protected Connection getConnection() {
		return (Connection) getModel();
	}
}